﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework;
namespace xpe
{
    /// <summary>
    /// The type of emitter
    /// </summary>
    public enum EmitterType { Point, Line, Rectangle, Ring }

    /// <summary>
    /// A particle emitter controls how particles get created and initialized
    /// </summary>
    public class ParticleEmitter
    {
        /// <summary>
        /// The type of emitter
        /// </summary>
        protected EmitterType type;

        /// <summary>
        /// The position of the emitter
        /// </summary>
        protected Vector3 translation;

        /// <summary>
        /// The scale of the emitter
        /// </summary>
        protected Vector3 scale;

        /// <summary>
        /// The rotation of the emitter
        /// </summary>
        protected Matrix rotation;

        /// <summary>
        /// The inital velocity of each particle
        /// </summary>
        protected Vector3 velocity;

        /// <summary>
        /// The minimum angle off the direction
        /// </summary>
        protected float minAngle;

        /// <summary>
        /// The maximum angle off the direction
        /// </summary>
        protected float maxAngle;

        /// <summary>
        /// The number of particles this emitter emittes per second
        /// </summary>
        protected int rate;

        /// <summary>
        /// True if all particles should be billboarded
        /// </summary>
        protected bool billboard;

        /// <summary>
        /// True if the particles for this emitter should respawn
        /// </summary>
        protected bool respawn;

        /// <summary>
        /// Create a new
        /// </summary>
        /// <param name="type">The type of emitter</param>
        /// <param name="particle">The particle that this emitter emits</param>
        public ParticleEmitter(EmitterType type)
        {  
            this.type = type;

            translation = new Vector3();
            scale = new Vector3();
            rotation = new Matrix();

            velocity = Vector3.Multiply(Vector3.UnitY, 1f);
            minAngle = maxAngle = 0f;

            rate = 128;
            billboard = false;
            respawn = true;
        }

        /// <summary>
        /// Sets the maximum and minimum distribution of the direction
        /// a particle can be created
        /// </summary>
        /// <param name="min">The minimum angle</param>
        /// <param name="max">The maximum angle</param>
        public void SetMinMaxAngles(float min, float max)
        {
            if (max < min)
                throw new ArgumentException("max < min");

            minAngle = min;
            maxAngle = max;
        }

        /// <summary>
        /// The type of particle emitter
        /// </summary>
        public EmitterType Type
        {
            get { return type; }
        }

        /// <summary>
        /// The position of this emitter
        /// </summary>
        public Vector3 Translation
        {
            get { return translation; }
            set { translation = value; }
        }

        /// <summary>
        /// The scale of this emitter
        /// </summary>
        public Vector3 Scale
        {
            get { return scale; }
            set { scale = value; }
        }

        /// <summary>
        /// The orientation of this emitter
        /// </summary>
        public Matrix Rotation
        {
            get { return rotation; }
            set { rotation = value; }
        }

        /// <summary>
        /// Returns the direction of this emitter
        /// </summary>
        public Vector3 Direction
        {
            get { return Vector3.Transform(Vector3.UnitY, rotation); }
        }

        /// <summary>
        /// The maximum angle
        /// </summary>
        public float MaxAngle
        {
            get { return maxAngle; }
        }

        /// <summary>
        /// The minimum angle
        /// </summary>
        public float MinAngle
        {
            get { return minAngle; }
        }

        /// <summary>
        /// Returns the number of particle that should be created per second
        /// </summary>
        public int Rate
        {
            get { return rate; }
            set
            {
                if (value < 1)
                    value = 1;

                rate = value;
            }
        }

        /// <summary>
        /// True if this emitter should respawn dead particles
        /// </summary>
        public bool Respawn
        {
            get { return respawn; }
            set { respawn = value; }
        }

        /// <summary>
        /// True if all particles from this emitter should be billboarded
        /// </summary>
        public bool IsBillboarding
        {
            get { return billboard; }
            set { billboard = value; }
        }
    }
}
